package ch.ti.bfh.app.loodel.web.controller;

import ch.ti.bfh.app.loodel.service.LearningEventInvitationData;
import ch.ti.bfh.app.loodel.service.MemberData;
import ch.ti.bfh.app.loodel.service.create.CreateLearningEventData;
import ch.ti.bfh.app.loodel.service.create.CreateLearningEventService;
import ch.ti.bfh.app.loodel.service.create.CreateTimeSlotData;
import ch.ti.bfh.app.loodel.web.model.CreateLearningEventModel;
import ch.ti.bfh.app.loodel.web.model.CreateTimeSlotDataWrapper;
import ch.ti.bfh.app.loodel.web.model.LearningEventWizardModel;
import ch.ti.bfh.app.loodel.web.utils.InvalidDateInvtervalException;
import org.apache.commons.collections.CollectionUtils;
import org.omnifaces.util.Messages;
import org.primefaces.event.SelectEvent;
import org.primefaces.model.DefaultScheduleEvent;
import org.primefaces.model.DefaultScheduleModel;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Component;

import javax.faces.context.FacesContext;
import javax.inject.Inject;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;


@Component
@Scope("request")
public class LearningEventCreateController implements Serializable {
    private final TimeSlotCreateController timeSlotCreateController;
    private final CreateLearningEventModel createLearningEventModel;
    private final CreateLearningEventService createLearningEventService;

    private final LearningEventWizardModel learningEventWizardModel;

    @Inject
    public LearningEventCreateController(CreateLearningEventModel createLearningEventModel, CreateLearningEventService createLearningEventService, TimeSlotCreateController timeSlotCreateController, LearningEventWizardModel learningEventWizardModel) {
        this.createLearningEventModel = createLearningEventModel;
        this.createLearningEventService = createLearningEventService;
        this.timeSlotCreateController = timeSlotCreateController;
        this.learningEventWizardModel = learningEventWizardModel;
    }

    public void init() {
        if (FacesContext.getCurrentInstance().isPostback() == false) {
            this.initCreateLearningEventModel();
            this.updateDefaultInvitationText();
            this.learningEventWizardModel.reset();
            timeSlotCreateController.init();
        }
    }

    public void initCreateLearningEventModel() {
        CreateLearningEventData createLearningEventData = new CreateLearningEventData();
        ArrayList<CreateTimeSlotData> timeSlots = new ArrayList<CreateTimeSlotData>();
        createLearningEventData.setTimeSlots(timeSlots);
        createLearningEventModel.setCreateLearningEventData(createLearningEventData);
        createLearningEventModel.setScheduleModel(new DefaultScheduleModel());
        LearningEventInvitationData createLearningEventInvitationData = new LearningEventInvitationData();
        createLearningEventInvitationData.setEmailList(new ArrayList<String>());
        createLearningEventModel.setLearningEventInvitationData(createLearningEventInvitationData);
    }

    public void applyTimeSlotForNewLearningEventAction() {
        try {
            DefaultScheduleEvent scheduleEvent = timeSlotCreateController.prepareAndGetNewTimeSlotAction();
            final CreateTimeSlotDataWrapper createTimeSlotDataWrapper = (CreateTimeSlotDataWrapper) scheduleEvent.getData();
            scheduleEvent.setTitle(createLearningEventModel.getCreateLearningEventData().getModuleName() + "@" + createTimeSlotDataWrapper.getLocationName());
            if (scheduleEvent.getId() == null) {
                createLearningEventModel.getScheduleModel().addEvent(scheduleEvent);
                createLearningEventModel.getCreateLearningEventData().getTimeSlots().add(createTimeSlotDataWrapper.getCreateTimeSlotData());
            } else {
                createLearningEventModel.getScheduleModel().updateEvent(scheduleEvent);
            }
        } catch (InvalidDateInvtervalException e) {
            Messages.addGlobalError("Invalid Time Range:" + e.getMessage());
        }

    }

    public List<MemberData> findMembers(String memberSearchString) {
        return this.createLearningEventService.findMemberDataForInvitation(memberSearchString);
    }

    public void applySelectedMemberForInvitation(SelectEvent selectEvent) {
        MemberData selectedMember = (MemberData) selectEvent.getObject();
        this.createLearningEventModel.getLearningEventInvitationData().getEmailList().add(selectedMember.geteMail());
    }

    public void updateDefaultInvitationText() {
        String invitationDefaultText = createLearningEventService.getInvitationDefaultText(createLearningEventModel.getCreateLearningEventData(), createLearningEventModel.getLearningEventInvitationData().getCustomText());
        createLearningEventModel.setLearningEventInvitationFixText(invitationDefaultText);
    }

    public void prepareLearningEventDefinitionStep() {
        this.learningEventWizardModel.setCurrentStep(LearningEventWizardModel.LearningEventWizardStep.DEFINE_LEARNING_EVENT);
    }

    public void prepareTimeSlotDefinitionStep() {
        this.learningEventWizardModel.setCurrentStep(LearningEventWizardModel.LearningEventWizardStep.DEFINE_TIMESLOTS);
    }

    public void prepareSendInvitationsStep() {
        if (CollectionUtils.isNotEmpty(createLearningEventModel.getCreateLearningEventData().getTimeSlots())) {
            this.updateDefaultInvitationText();
            this.learningEventWizardModel.setCurrentStep(LearningEventWizardModel.LearningEventWizardStep.SEND_INVITATIONS);
        } else {
            Messages.addGlobalError("You need to define at least one Time Slot");
        }
    }

    public String createAndSaveLearningEvent() {
        String learningEventId = createLearningEventService.createNewLearningEvent(createLearningEventModel.getCreateLearningEventData());
        Messages.addFlashGlobalInfo("You're Learning Event has been created!");
        return "/vote/learningEventVote.xhtml?faces-redirect=true&id=" + learningEventId;
    }
}
